using System;
using System.Windows.Forms;

using System.ServiceProcess;
using Model;
using System.Xml;
using System.Runtime.Remoting.Channels;
using System.Runtime.Remoting.Channels.Http;

namespace MizClient
{
	/// <summary>
	/// Has the main method , bootstraps the application.
	/// All program configuration information is managed by this class.
	/// </summary>
	public class MizClient
	{
		public static string ConfigFile=AppDomain.CurrentDomain.SetupInformation.ApplicationBase+"Mizaniya.config";
		
		private static XmlDocument xmlConfigFile=new XmlDocument();

		public static bool isServiceLocal()
		{
			if (ServerIP.Equals("localhost") || ServerIP.Equals("127.0.0.1")) return true; else return false;
		}

		/// <summary>
		/// Save user name & password to config file
		/// </summary>
		/// <param name="currentUser"></param>
		public static void RememberUserCredentials(UserIdentity currentUser)
		{
			RememberedUserName = currentUser.Name;
			RememberedUserPassword = currentUser.Password;

			//Save username
			XmlNode rememberedUserName = xmlConfigFile.SelectSingleNode("/myMizaniya/client/rememberedUserName");
			rememberedUserName.InnerText=RememberedUserName;
			xmlConfigFile.Save(ConfigFile);

			//Save password
			XmlNode rememberedPassword = xmlConfigFile.SelectSingleNode("/myMizaniya/client/rememberedPassword");
			rememberedPassword.InnerText = RememberedUserPassword;
			xmlConfigFile.Save(ConfigFile);
			
		}

		public static string ServerIP 
		{
			get 
			{
				return xmlConfigFile.SelectSingleNode("/myMizaniya/client/serverIP").InnerText;

			}
			set 
			{
				XmlNode serverIP = xmlConfigFile.SelectSingleNode("/myMizaniya/client/serverIP");
				serverIP.InnerText=value;
				xmlConfigFile.Save(ConfigFile);
			}
		}

		public static string ServerPort 
		{
			get 
			{
				return xmlConfigFile.SelectSingleNode("/myMizaniya/port").InnerText;
			}
			set
			{
				XmlNode serverPort = xmlConfigFile.SelectSingleNode("/myMizaniya/port");
				serverPort.InnerText=value;
				xmlConfigFile.Save(ConfigFile);
			}
			
		}

		public static string EndPoint 
		{
			get 
			{
				return xmlConfigFile.SelectSingleNode("/myMizaniya/endPoint").InnerText;
			}
			set
			{
				XmlNode endPoint = xmlConfigFile.SelectSingleNode("/myMizaniya/endPoint");
				endPoint.InnerText=value;
				xmlConfigFile.Save(ConfigFile);
			}
			
		}

		public static bool IsServiceAlwaysOn 
		{
			get
			{
				bool result;
				try
				{
					result = Boolean.Parse(xmlConfigFile.SelectSingleNode("/myMizaniya/isServiceAlwaysOn").InnerText);
				}
				catch (Exception e)
				{
					result = true; //default, if nothing defined
				}
				return result;
			}
			set
			{
				XmlNode isServiceAlwaysOn = xmlConfigFile.SelectSingleNode("/myMizaniya/isServiceAlwaysOn");
				isServiceAlwaysOn.InnerText=value.ToString();
				xmlConfigFile.Save(ConfigFile);
			}
			
		}
		
		public static bool IsFirstRun
		{
			get
			{
				bool result;
				try
				{
					result = Boolean.Parse(xmlConfigFile.SelectSingleNode("/myMizaniya/isFirstRun").InnerText);
				}
				catch (Exception e)
				{
					result = false; //default, if nothing defined
				}
				return result;
				
			}
			set
			{
				XmlNode isServiceAlwaysOn = xmlConfigFile.SelectSingleNode("/myMizaniya/isFirstRun");
				isServiceAlwaysOn.InnerText=value.ToString();
				xmlConfigFile.Save(ConfigFile);
			}
			
		}


		/// <summary>
		/// erases username and password from config file
		/// </summary>
		public static void ForgetUserCredentials()
		{
			RememberedUserName ="";
			RememberedUserPassword ="";

			//Save username
			XmlNode rememberedUserName = xmlConfigFile.SelectSingleNode("/myMizaniya/client/rememberedUserName");
			rememberedUserName.InnerText=RememberedUserName;
			xmlConfigFile.Save(ConfigFile);

			//Save password
			XmlNode rememberedPassword = xmlConfigFile.SelectSingleNode("/myMizaniya/client/rememberedPassword");
			rememberedPassword.InnerText = RememberedUserPassword;
			xmlConfigFile.Save(ConfigFile);
		}		

		/// <summary>
		/// gets user name and password from config file
		/// </summary>
		/// <returns></returns>
		public static bool isUserCredentialsRemembered()
		{
			RememberedUserName = xmlConfigFile.SelectSingleNode("/myMizaniya/client/rememberedUserName").InnerText;
			RememberedUserPassword = xmlConfigFile.SelectSingleNode("/myMizaniya/client/rememberedPassword").InnerText;
			if(RememberedUserName.Length != 0)
				return true;
			
			return false;
		}



		/// <summary>
		/// If the database is at localhost, start the service.
		/// </summary>
		public static void  StartService()
		{
			localService = new ServiceController();
			localService.ServiceName="MizaniyaService";
	

			if (localService.Status == ServiceControllerStatus.Stopped)
			{
				// Start the service if the current status is stopped.

				Console.WriteLine("Starting the service...");
				try 
				{
					// Start the service, and wait until its status is "Running".
					localService.Start();
					localService.WaitForStatus(ServiceControllerStatus.Running);
   
					// Display the current service status.
					Console.WriteLine("The Alerter service status is now set to {0}.", 
						localService.Status.ToString());
				}
				catch (InvalidOperationException)
				{
					Console.WriteLine("Could not start the service.");
				}
			}
		}

		/// <summary>
		/// If the service is at localhost, stop the service before exiting the client.
		/// </summary>
		public static void StopService()
		{
			localService.Stop();
		}



		
		
		
		public static string ServerUri;
		public static string RememberedUserName;
		public static string RememberedUserPassword;
	
		
		private static ServiceController localService;

		/// <summary>
		/// disconnects from the service
		/// </summary>
		public static void Disconnect()
		{
			

		}

		/// <summary>
		/// Exits the system
		/// </summary>
		public static void Exit()
		{
			if (!IsServiceAlwaysOn && isServiceLocal()) StopService();
			Application.Exit();
			
		}


		public static void Main()
		{

			// Read contents of the client config file to get information about the server
			// TODO: if the document is not available, proceed to first run state
			xmlConfigFile.Load(ConfigFile);
				

					
			
			
						
			if (IsFirstRun)
			{
				View.SetupView configForm = new View.SetupView();
				configForm.ShowDialog();

				if (configForm.DialogResult.Equals(System.Windows.Forms.DialogResult.Cancel))	// if the config file was not set
				{
					Application.Exit();     
               		return;																		   
				}

				IsFirstRun=false;
			}

			ServerUri = "http://"+ServerIP+":"+ServerPort+"/"+EndPoint;	 // TODO: if the config file is corrupt	

			#if (!DEBUG)  
			if (isServiceLocal() )
			{
				StartService(); // start the service
			}

			#endif
			

#if (DEBUG_LOCALDB)
			IRemoteService remoteService = new DatabaseManagerADO("MizaniyaDB.xml","MizaniyaDB.xsd"); //debugging only
#else
			// instantiate the server object. Establish connection to the server
			HttpChannel channel = new HttpChannel();
			ChannelServices.RegisterChannel(channel);
			object remoteObj= Activator.GetObject(typeof(Model.IRemoteService),ServerUri);
			IRemoteService remoteService = remoteObj as IRemoteService;
			//TODO: handle server unreachable
#endif		


			

			Model.UserManager myUser = new Model.UserManager(remoteService);

			


			
			View.SystemView myhomePage = new View.SystemView(myUser);

#if (!DEBUG)
            try
            {
                Application.Run(myhomePage);
            }
            catch
            {
               //TODO: add this to logs
            }
#else
            Application.Run(myhomePage);
#endif

 
		}
	}
}
